package com.xbb.monitor.service;

import com.xbb.monitor.entity.Cpu;
import com.xbb.monitor.entity.echarts.AreaStyle;
import com.xbb.monitor.entity.echarts.LineBean;
import com.xbb.monitor.entity.echarts.LineData;
import com.xbb.monitor.entity.echarts.Normal;
import com.xbb.monitor.repository.CpuRepository;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.PersistenceContexts;
import javax.persistence.Query;
import java.text.SimpleDateFormat;
import java.util.*;

@Service
public class CpuService {
    @Autowired
    private CpuRepository cpuRepository;
    @Autowired
    private MemInfoService memInfoService;
    @Autowired
    private LoadAverageService loadAverageService;
    @Autowired
    private DiskService diskService;
    @Autowired
    private NetworkService networkService;

    @PersistenceContext
    private EntityManager entityManager;

    public void test(){
        String timeFormat = "%Y-%m-%d";
        String time = "2017-09-08";
        List<Cpu> cpuList = cpuRepository.findByTime(timeFormat,time);
        System.out.println(cpuList.size());
    }

    public Map<String,Object> daysData(String dataFlag){
        Map<String,Object> map = new HashMap<String,Object>();

        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Calendar calendar = Calendar.getInstance();
        String endTime = sdf.format(calendar.getTime());

        int interval = getInterval(dataFlag);
        if(interval == 0){
            return null;
        }
        calendar = calculateTime(calendar,dataFlag);
        String startTime = sdf.format(calendar.getTime());

        //cpu
        List<LineBean> cpus = cpuData(calendar,interval,sdf);
        //内存
        List<LineBean> memInfo = memInfoService.getData(calendar,interval,sdf);
        //负载
        List<LineBean> loadAverage = loadAverageService.getData(calendar,interval,sdf);
        //硬盘
        List<String> paths = diskService.getPath();
        if(paths != null && paths.size() > 0){
            Map<String,Object> map1 = diskService.getDataByPath(calendar,interval,sdf,paths.get(0));
            map.putAll(map1);
//            map.put("dataDisk",map1.get("dataDisk"));
//            map.put("kbs",map1.get("kbs"));
//            map.put("rws",map1.get("rws"));
        }
        //网络
        List<String> networkNames = networkService.getNetworkName();
        if(networkNames != null && networkNames.size() > 0){
            Map<String,Object> map2 = networkService.getData(calendar,interval,sdf,networkNames.get(0));
            map.putAll(map2);
//            map.put("results",map2.get("results"));
//            map.put("all",map2.get("all"));
        }

        map.put("startTime",startTime);
        map.put("endTime",endTime);
        map.put("dataCpu",cpus);
        map.put("dataMemInfo",memInfo);
        map.put("dataLoadAverage",loadAverage);
        map.put("diskPath",paths);
        map.put("networkName",networkNames);



        return map;
    }

    public List<LineBean> cpuData(Calendar calendar,int interval,SimpleDateFormat sdf){
        String sql = "SELECT id,user,nice,system,iowait,steal,idle,time FROM (\n" +
                "  SELECT b.*,@rownum \\:= @rownum + 1 AS rownum,\n" +
                "  @ptime2 \\:=b.time as ptime2,\n" +
                "  if(TIMESTAMPDIFF(MINUTE,@ptime,b.time)<?2,@ptime=null,@ptime\\:=@ptime2) AS ptime FROM\n" +
                "(SELECT * FROM t_cpu WHERE TIME >= ?1  ORDER BY time) b,\n" +
                "(SELECT @rownum \\:= 0,@ptime\\:= NULL ,@rank\\:=0,@ptime2\\:=NULL ) a\n" +
                ") AS c WHERE ptime IS NOT NULL";

        Query query = entityManager.createNativeQuery(sql,Cpu.class);

        query.setParameter(1,calendar.getTime());
        query.setParameter(2,interval);
        List<Cpu> cpus = query.getResultList();

        List<LineBean> lineBeans = new ArrayList<LineBean>();
        AreaStyle areaStyle = new AreaStyle(new Normal());
        LineBean lineUser = new LineBean("user","line","cpu",areaStyle);
        LineBean lineNice = new LineBean("nice","line","cpu",areaStyle);
        LineBean lineSystem = new LineBean("system","line","cpu",areaStyle);
        LineBean lineIowait = new LineBean("iowait","line","cpu",areaStyle);
        LineBean lineSteal = new LineBean("steal","line","cpu",areaStyle);
        LineBean lineIdle = new LineBean("idle","line","cpu",areaStyle);

        List<String[]> datasUser = new ArrayList<String[]>();
        List<String[]> datasNice = new ArrayList<String[]>();
        List<String[]> datasSystem = new ArrayList<String[]>();
        List<String[]> datasIowait = new ArrayList<String[]>();
        List<String[]> datasSteal = new ArrayList<String[]>();
        List<String[]> datasIdle = new ArrayList<String[]>();
        for(Cpu cpu : cpus){
            String[] dataUser = {sdf.format(cpu.getTime()),cpu.getUser()+""};
            String[] dataNice = {sdf.format(cpu.getTime()),cpu.getNice()+""};
            String[] dataSystem = {sdf.format(cpu.getTime()),cpu.getSystem()+""};
            String[] dataIowait = {sdf.format(cpu.getTime()),cpu.getIowait()+""};
            String[] dataSteal = {sdf.format(cpu.getTime()),cpu.getSteal()+""};
            String[] dataIdle = {sdf.format(cpu.getTime()),cpu.getIdle()+""};

            datasUser.add(dataUser);
            datasNice.add(dataNice);
            datasSystem.add(dataSystem);
            datasIowait.add(dataIowait);
            datasSteal.add(dataSteal);
            datasIdle.add(dataIdle);
        }

        lineUser.setData(datasUser);
        lineNice.setData(datasNice);
        lineSystem.setData(datasSystem);
        lineIowait.setData(datasIowait);
        lineSteal.setData(datasSteal);
        lineIdle.setData(datasIdle);

        lineBeans.add(lineUser);
        lineBeans.add(lineNice);
        lineBeans.add(lineSystem);
        lineBeans.add(lineIowait);
        lineBeans.add(lineSteal);
        lineBeans.add(lineIdle);

        return lineBeans;
    }

    public Calendar calculateTime(Calendar calendar,String dataFlag){
        if("oneHour".equals(dataFlag)){
            calendar.set(Calendar.HOUR_OF_DAY,calendar.get(Calendar.HOUR_OF_DAY)-1);
        }else if("sixHours".equals(dataFlag)){
            calendar.set(Calendar.HOUR_OF_DAY,calendar.get(Calendar.HOUR_OF_DAY)-3);
        }else if("twelveHours".equals(dataFlag)){
            calendar.set(Calendar.HOUR_OF_DAY,calendar.get(Calendar.HOUR_OF_DAY)-12);
        }else if("oneDay".equals(dataFlag)){
            calendar.set(Calendar.DAY_OF_MONTH,calendar.get(Calendar.DAY_OF_MONTH)-1);
        }else if("threeDays".equals(dataFlag)){
            calendar.set(Calendar.DAY_OF_MONTH,calendar.get(Calendar.DAY_OF_MONTH)-3);
        }else if("sevenDays".equals(dataFlag)){
            calendar.set(Calendar.DAY_OF_MONTH,calendar.get(Calendar.DAY_OF_MONTH)-7);
        }else if("fourteenDays".equals(dataFlag)){
            calendar.set(Calendar.DAY_OF_MONTH,calendar.get(Calendar.DAY_OF_MONTH)-14);
        }else{
            return null;
        }
        return calendar;
    }

    public int getInterval(String dataFlag){
        int interval = 2;
        if("oneHour".equals(dataFlag)){
            interval = 2;
        }else if("sixHours".equals(dataFlag)){
            interval = 7;
        }else if("twelveHours".equals(dataFlag)){
            interval = 24;
        }else if("oneDay".equals(dataFlag)){
            interval = 48;
        }else if("threeDays".equals(dataFlag)){
            interval = 144;
        }else if("sevenDays".equals(dataFlag)){
            interval = 336;
        }else if("fourteenDays".equals(dataFlag)){
            interval = 672;
        }else{
            return 0;
        }
        return interval;
    }



}
